package api.apiservice.apiopenplat.service.Impl;
import api.apiservice.apiopenplat.entity.ApiInfo;
import api.apiservice.apiopenplat.pojo.condition.ApiInfoIndex;
import api.apiservice.apiopenplat.mapper.ApiInfoMapper;
import api.apiservice.apiopenplat.service.IApiInfoService;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.crypto.asymmetric.Sign;
import cn.hutool.crypto.asymmetric.SignAlgorithm;
import cn.hutool.jwt.JWT;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import api.apiservice.apiopenplat.Utils.HttpUtils;
import api.apiservice.apiopenplat.common.unifyDataForm.Exception.ExceptionEnu;
import api.apiservice.apiopenplat.common.unifyDataForm.Exception.myException;
import api.apiservice.apiopenplat.pojo.access.accessPromission;
import api.apiservice.apiopenplat.pojo.add.ApiAdd;
import api.apiservice.apiopenplat.pojo.apiRequest.apiRequest;
import api.apiservice.apiopenplat.pojo.update.ApiUpdate;
import io.swagger.annotations.Api;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;

import java.util.HashMap;
import java.util.List;

/**
 * <p>
 *  服务实现类
 * </p>
 *
 * @author Tangshen
 * @since 2022-11-11
 */

@DubboService
public class ApiInfoServiceImpl extends ServiceImpl<ApiInfoMapper, ApiInfo> implements IApiInfoService {

    @Autowired
    private RedisTemplate redisTemplate;

    @Autowired
    private ApiInfoMapper apiInfoMapper;


    /**
     *
     * 添加Api信息
     *
     * */
    @Override
    public boolean saveApiInfo(ApiInfo apiAdd) {
        ApiInfo apiInfo = new ApiInfo();
        apiAdd.setAUsedStatus(0);
        BeanUtils.copyProperties(apiAdd,apiInfo);
        return this.save(apiInfo);
    }

    /**
     *
     * 更改API 信息
     *
     * */
    @Override
    public boolean updateApiInfoById(ApiUpdate apiUpdate) {
        ApiInfo apiInfo = new ApiInfo();
        //TODO 判断API URI是否合法（进行http调用查看是否能够通过)
        BeanUtils.copyProperties(apiUpdate, apiInfo);
        return this.updateById(apiInfo);
    }

    @Override
    public boolean delApiInfo(List<Long> idList) {
        int i = this.baseMapper.deleteBatchIds(idList);
        if (i == 0) {
            return false;
        }
            return true;
        }

    /**
     *
     * APi是否存在
     *
     * */
    @Override
    public ApiInfo isExistApi(Long requestId) {
        QueryWrapper<ApiInfo> queryWrapper = new QueryWrapper<ApiInfo>();
        queryWrapper.eq("a_Id",requestId);
        queryWrapper.eq("a_used_status",1);
        ApiInfo apiInfoIndex = this.baseMapper.selectOne(queryWrapper);
        if (apiInfoIndex == null){
            return null;
        }
        return apiInfoIndex;
    }

    @Override
    public ApiInfo searchApiById(Long apiId) {
        return this.baseMapper.selectById(apiId);
    }

    @Override
    public ApiInfo searchApiByUri(String apiUri) {
        QueryWrapper<ApiInfo> queryWrapper = new QueryWrapper<ApiInfo>();
        queryWrapper.eq("a_uri",apiUri);
        ApiInfo apiInfo = baseMapper.selectOne(queryWrapper);
        return apiInfo;
    }

    /**
     *
     * 获取许可证  accesskey accessSecret
     *
     * */
    @Override
    public accessPromission getPermission(Long userId) {
        accessPromission permission = this.baseMapper.getPermissionById(userId);
        return permission;
    }

    @Override
    public boolean checkPermiession(HashMap<String, String> requestMap) {
        accessPromission userPermission = this.baseMapper.getPermissionById(Long.valueOf(requestMap.get("userId")));
        //校验用户信息
        //判断调用时长
        if(Long.valueOf(requestMap.get("timeDifference"))/1000  <  120){
            throw new myException(ExceptionEnu.REQUEST_ERROR_TIME);
        }
        //判断accesskey是否正确
        if (userPermission.getAccessKey().isEmpty() && userPermission.getAccessKey().equals(requestMap.get("accessKey"))){
            throw  new myException(ExceptionEnu.REQUEST_ERROR_KEY);
        }
        Sign sign = SecureUtil.sign(SignAlgorithm.MD5withRSA);
        byte[] signed = userPermission.getAccessSecret().getBytes();

        //校验accessSecret
        if (!sign.verify(signed, userPermission.getKeySalt().getBytes())){
            throw  new myException(ExceptionEnu.REQUEST_ERROR_VER);
        }

        return true;
    }

    /**
     *
     * 校验API 信息
     *
     * */
    @Override
    public HashMap<String,String> checkApiMessage(Long requestId) {
        apiRequest invokeApi = this.baseMapper.getInvokeApi(requestId);
        if (invokeApi.getAUsedStatus() == 0){
            throw  new myException(ExceptionEnu.REQUEST_ERROR_USE);
        }
        HashMap<String,String> apiUrl = new HashMap<String,String>();
        apiUrl.put("method",invokeApi.getAMethod());
        apiUrl.put("url",invokeApi.getAUri());
        return apiUrl;
    }

    @Override
    public List<ApiInfoIndex> pageApiList() {
        return apiInfoMapper.getApiInfo();
    }
}
